#include "intEvent.h"
#include <queue.h>
#include <main.h>

static QueueHandle_t keyEventQueue;
static TaskHandle_t intEventTaskHandle;

void Key0_handler(bool pressed)
{
    keyEvent_t e = {.isPressed = pressed,
                    .keyID = EXINT_KEY0};

    xQueueSendFromISR(keyEventQueue, (void *)&e, 0);
}

void Key1_handler(bool pressed)
{
    keyEvent_t e = {.isPressed = pressed,
                    .keyID = EXINT_KEY1};

    xQueueSendFromISR(keyEventQueue, (void *)&e, 0);
}

#define BOOT_EN (0)

#if BOOT_EN == 1

typedef void (*pFunc)(void);
pFunc func;

#elif BOOT_EN == 2

void (*jump)();

#endif

void keyIntQueueEvent(void *params)
{

    keyEvent_t event;

    while (1)
    {

        // printf("wait key press\r\n");
        if (xQueueReceive(keyEventQueue, &event, portMAX_DELAY) == pdPASS)
        {

            switch (event.keyID)
            {
            case EXINT_KEY0:
                if (event.isPressed == true)
                {
                    printf("key0 pressed\r\n");

#if BOOT_EN == 1

                    // 设置MSP
                    __set_MSP(0x8000000);
                    jump = (void (*)()) * (uint32_t *)(0x8000000 + 0x4);
                    __disable_irq();
                    jump();
#elif BOOT_EN == 2

                    // 设置MSP
                    __set_MSP(0x8000000);
                    func = (pFunc) * (uint32_t *)(0x8000000 + 0x4);
                    __disable_irq();
                    func();
#endif
                }
                else
                {
                    printf("key0 release\r\n");
                    //

                    uint8_t alltask[512] = {0};
                    // TaskHandle_t alltask[50] = {0};
                    vTaskList((char *)alltask);

                    printf("%s\r\n", alltask);
                }

                break;
            case EXINT_KEY1:
                if (event.isPressed == true)
                {
                    printf("key1 pressed\r\n");
                }
                else
                {
                    printf("key1 release\r\n");

                    // vTaskDelete(intEventTaskHandle);
                }
                break;

            default:
                break;
            }
        }
    }
}

HAL_StatusTypeDef initKeyIntEventTask(void)
{

    if (xTaskCreate(keyIntQueueEvent, "keyIntEvent", 128, NULL, 5, &intEventTaskHandle) != pdPASS)
    {
        printf("create keyIntEventTask failed\r\n");
        return HAL_ERROR;
    }

    return HAL_OK;
}

HAL_StatusTypeDef initKeyIntEventQueue(void)
{
    keyEventQueue = xQueueCreate(128, sizeof(keyIntId_e));
    if (keyEventQueue == NULL)
    {
        return HAL_ERROR;
    }

    return HAL_OK;
}

void HAL_GPIO_EXTI_Callback(uint16_t GPIO_Pin)
{
    if (GPIO_Pin == KEY0_Pin)
    {
        if (HAL_GPIO_ReadPin(KEY0_GPIO_Port, KEY0_Pin) == GPIO_PIN_SET)
        {
            Key0_handler(true);
        }
        else
        {
            Key0_handler(false);
        }
    }
    else if (GPIO_Pin == KEY1_Pin)
    {
        if (HAL_GPIO_ReadPin(KEY1_GPIO_Port, KEY1_Pin) == GPIO_PIN_SET)
        {
            Key1_handler(true);
        }
        else
        {
            Key1_handler(false);
        }
    }
}
